home *** CD-ROM | disk | FTP | other *** search
/ Windows Expert / Windows Expert.iso / windownt / cxxp4w.zip / CHAP03 / WINDOW.CPP next >
C/C++ Source or Header  |  1993-03-11  |  8KB  |  278 lines

  1. #include "window.hpp"
  2.  
  3. ATOM aProp, aPropHigh;
  4.  
  5. #if defined( PTR16) || defined (WIN32)
  6.   #define PUTPWIN(hWnd,this) \
  7.     SetProp(hWnd,(LPSTR)MAKELONG(aProp,0),(HANDLE)this)
  8.   #define GETPWIN(hWnd) \
  9.     (Window *)GetProp(hWnd,(LPSTR)MAKELONG(aProp,0))
  10.   #define DELPWIN(hWnd) \
  11.     (Window *)RemoveProp(hWnd,(LPSTR)MAKELONG(aProp,0))
  12. #else
  13.   #define PUTPWIN(hWnd,this)\
  14.     SetProp(hWnd,(LPSTR)MAKELONG(aProp,0),(HANDLE)this);\
  15.     SetProp(hWnd,(LPSTR)MAKELONG(aPropHigh,0),\
  16.     (HANDLE)((DWORD)this >>16))
  17.   #define GETPWIN(hWnd) (Window *)\
  18.     ((DWORD)GetProp(hWnd,(LPSTR)MAKELONG(aProp,0))|\
  19.     ((DWORD)GetProp(hWnd,(LPSTR)MAKELONG(aPropHigh,0)) <<16))
  20.   #define DELPWIN(hWnd) (Window *)\
  21.     ((DWORD)RemoveProp(hWnd,(LPSTR)MAKELONG(aProp,0))|\
  22.     ((DWORD)RemoveProp(hWnd,(LPSTR)MAKELONG(aPropHigh,0)) <<16))
  23. #endif // PTR16
  24.  
  25. // Routines to associate instance pointers with windows
  26. void PutWin(HWND hWnd, Window * pWin) { PUTPWIN(hWnd,pWin);};
  27. Window * GetWin(HWND hWnd) {return GETPWIN(hWnd);};
  28. Window*  DelWin(HWND hWnd) {return DELPWIN(hWnd);};
  29.  
  30. //#ifdef WIN32
  31. //  WNDPROC Window::Handler;
  32. //#else
  33.   FARPROC Window::Handler;        // proc instance for CPPWinProc
  34. //#endif
  35. HANDLE Window::hAccel;          // Current accelerator table
  36.  
  37. //  Set window message proc to CPPWinProc
  38. void Window::SetHandler()
  39. {
  40. //#ifdef WIN32
  41. //  DefaultHandler = (WNDPROC) GetWindowLong(hWnd,GWL_WNDPROC);
  42. //#else
  43.   DefaultHandler = (FARPROC) GetWindowLong(hWnd,GWL_WNDPROC);
  44. //#endif
  45.   SetWindowLong(hWnd,GWL_WNDPROC,(LONG) Handler);
  46. PUTPWIN(hWnd,(HANDLE) this);
  47. }
  48.  
  49. // Create a window
  50. void Window::Create(LPSTR caption, LONG style, int x, int y,
  51.         int width, int height, HWND hPwnd, HMENU hMenu)
  52. {
  53.  
  54.   WNDCLASS wc;
  55.   wc.style         = 0;
  56.   wc.lpfnWndProc   = (WNDPROC) DefWindowProc;
  57.   wc.cbClsExtra    = 0;
  58.   wc.cbWndExtra    = 0;
  59.   wc.hInstance     = hInst;
  60.   wc.hIcon         = LoadIcon(NULL,IDI_APPLICATION);
  61.   wc.hCursor       = LoadCursor(NULL,IDC_ARROW);
  62.   wc.hbrBackground = (HBRUSH)(COLOR_WINDOW+1);
  63.   wc.lpszMenuName  = 0;
  64.  
  65.   hWnd = CreateWindow(Register(wc),
  66.                         caption,style,x,y,width,height,
  67.                         hPwnd,hMenu,hInst,NULL);
  68.  
  69.   if (!hWnd) Error(IDS_APPLERROR, (LPSTR)"Window Creation");
  70.   SetHandler();
  71. }
  72.  
  73. Window::Window() {
  74.   hWnd=0;
  75.   if (!Handler) {
  76.   #ifdef WIN32
  77.     Handler = (FARPROC)CPPWinProc;
  78.   #else
  79.     Handler = MakeProcInstance((FARPROC)CPPWinProc, hInst);
  80.   #endif
  81.     aProp=AddAtom("pWindow");
  82.     aPropHigh=AddAtom("pWindowHigh");
  83.   }
  84. }
  85.  
  86. LPSTR Window::Register(WNDCLASS& wc) {
  87.     Error(IDS_APPLERROR,(LPSTR)"No Register method");
  88. return NULL;
  89. }
  90.  
  91. Window::~Window()
  92. {
  93.  
  94.   if (hWnd) {
  95.     Show(SW_HIDE);
  96.     //Destroy instances associated with child windows
  97.     HWND hCwnd= GetWindow (hWnd, GW_CHILD);
  98.     while ( hCwnd ){
  99.        Window * pWin=(Window*) GETPWIN(hCwnd);
  100.        do {
  101.             hCwnd=GetWindow(hCwnd,GW_HWNDNEXT);
  102.        } while (hCwnd  && GetParent(hCwnd)!=hWnd);
  103.        if (pWin) delete pWin;
  104.     }
  105.  
  106.     if (DELPWIN(hWnd) && DefaultHandler)
  107.       SetWindowLong(hWnd,GWL_WNDPROC,(LONG) DefaultHandler);
  108.     //if this is the top level window quit the application
  109.     if (!GetParent(hWnd)) PostQuitMessage(0);
  110.     DestroyWindow(hWnd);
  111.     hWnd=0;
  112.   }
  113. }
  114.  
  115. // The application message loop
  116. int Window::MessageLoop()
  117. {
  118.     MSG msg;
  119.     while (GetMessage(&msg, NULL, 0, 0)) {
  120.       if (!hAccel ||
  121.         !TranslateAccelerator (hWnd, hAccel, &msg)){
  122.         TranslateMessage (&msg);
  123.         DispatchMessage (&msg);
  124.       }
  125.     }
  126.     return msg.wParam;
  127. }
  128.  
  129.  
  130. // The window message function, translates messages
  131. // to calls to virtual functions
  132. LONG Window::MessageProc( HWND hWnd, UINT msg, Event& evt)
  133. {
  134.   POINT Pt;
  135.  
  136.   switch (msg){
  137.  
  138.     case WM_QUERYENDSESSION:
  139.       // OK to end Windows session?
  140.       return QueryClose();
  141.  
  142.     case WM_CLOSE:
  143.       // if OK delete this instance
  144.       if (QueryClose ()) delete this;
  145.       return TRUE;
  146.       
  147.     case WM_DESTROY:
  148.       if (DELPWIN(hWnd) && DefaultHandler)
  149.         SetWindowLong(hWnd,GWL_WNDPROC,(LONG) DefaultHandler);
  150.       Window::hWnd=0;
  151.       delete this;
  152.       break;
  153.           
  154.     case WM_INITMENU:
  155.       return InitMenu((HMENU)evt.wParam);
  156.  
  157.     case WM_SIZE:
  158.       return Size(LOWORD(evt.lParam),
  159.                   HIWORD(evt.lParam),evt.wParam);
  160.  
  161.     case WM_PAINT:
  162.       return Paint();
  163.  
  164.     case WM_SETFOCUS:
  165.       return SetFocus((HWND)evt.wParam);
  166.  
  167.     case WM_KILLFOCUS:
  168.       return KillFocus((HWND)evt.wParam);
  169.  
  170.     case WM_CHAR:
  171.       return Char(evt.wParam, LOWORD(evt.lParam));
  172.  
  173.     case WM_KEYDOWN:
  174.       if (KeyDown(evt.wParam, 
  175.          *(KEYCODES*)&evt.lParam)) return TRUE;
  176.       return FALSE;
  177.  
  178.     case WM_LBUTTONDOWN:
  179.       Pt.x=LOWORD(evt.lParam); Pt.y=HIWORD(evt.lParam);
  180.       return LButtonDown(Pt, evt.wParam);
  181.  
  182.     case WM_LBUTTONUP:
  183.       Pt.x=LOWORD(evt.lParam); Pt.y=HIWORD(evt.lParam);
  184.       return LButtonUp(Pt, evt.wParam);
  185.  
  186.     case WM_LBUTTONDBLCLK:
  187.       Pt.x=LOWORD(evt.lParam); Pt.y=HIWORD(evt.lParam);
  188.       return LButtonDblClk(Pt, evt.wParam);
  189.       
  190.     case WM_RBUTTONDOWN:
  191.       Pt.x=LOWORD(evt.lParam); Pt.y=HIWORD(evt.lParam);
  192.       return RButtonDown(Pt, evt.wParam);
  193.  
  194.     case WM_RBUTTONUP:
  195.       Pt.x=LOWORD(evt.lParam); Pt.y=HIWORD(evt.lParam);
  196.       return RButtonUp(Pt, evt.wParam);
  197.       
  198.     case WM_MOUSEMOVE:
  199.       Pt.x=LOWORD(evt.lParam); Pt.y=HIWORD(evt.lParam);
  200.       return MouseMove(Pt, evt.wParam);
  201.       
  202.     case WM_MOUSEACTIVATE:
  203.       MouseActivate((HWND)evt.wParam, LOWORD(evt.lParam));
  204.       if(DefaultHandler)
  205.     return CallWindowProc (DefaultHandler,
  206.            hWnd, msg, evt.wParam, evt.lParam);
  207.       else return FALSE;
  208.  
  209.  
  210.     case WM_COMMAND:
  211.     {
  212.       WORD wNotifyCode;         // notification code
  213.       WORD wID;                 // item, control, or accelerator ID
  214.       HWND hWndCtl;             // handle of control
  215.  
  216. #ifdef WIN32
  217.       wNotifyCode = HIWORD(evt.wParam); 
  218.       wID = LOWORD(evt.wParam); 
  219.       hWndCtl = (HWND) evt.lParam; 
  220. #else
  221.       wID = (int) evt.wParam; 
  222.       hWndCtl = (HWND) LOWORD(evt.lParam);
  223.       wNotifyCode = HIWORD(evt.lParam); 
  224. #endif
  225.       return Command(wID,wNotifyCode, hWndCtl);
  226.     }
  227.  
  228.     default:
  229.       if (DefaultHandler)
  230.     return CallWindowProc (DefaultHandler,
  231.            hWnd, msg, evt.wParam, evt.lParam);
  232.   } // switch
  233.   return FALSE;
  234. } // MessageProc
  235.  
  236. BOOL Window::Size(UINT Width, UINT Height, UINT Type) {
  237.   if (!DefaultHandler) return FALSE;
  238.   return CallWindowProc (DefaultHandler,
  239.          hWnd, WM_SIZE, Type, MAKELONG(Width, Height));
  240. }
  241.  
  242. BOOL Window::Paint() {
  243.   if (!DefaultHandler) return FALSE;
  244.   return CallWindowProc (DefaultHandler, hWnd, WM_PAINT, 0,0);
  245. }
  246.  
  247. BOOL Window::Command( UINT Id, UINT Code, HWND hControl) {
  248.   if (!DefaultHandler) return FALSE;
  249. #ifdef WIN32
  250.   return CallWindowProc (DefaultHandler,
  251.     hWnd, WM_COMMAND, MAKELONG(Id, Code), (DWORD)hControl);
  252. #else
  253.   return CallWindowProc (DefaultHandler,
  254.     hWnd, WM_COMMAND, Id, MAKELONG(hControl, Code));
  255. #endif
  256. }
  257.  
  258. LONG CALLBACK CPPWinProc(HWND hWnd, UINT Message,
  259.                UINT wParam,LONG lParam)
  260. {
  261.   Window* pWin = GETPWIN(hWnd);
  262.   Event evt(wParam,lParam);
  263.   if (pWin) {
  264.     // There is a C++ instance for the window
  265.     return pWin->MessageProc(hWnd,Message,evt);
  266.   }
  267.   else return FALSE;
  268. } // CPPWinProc
  269.  
  270. void Window::Move(RECT * rc, BOOL repaint) {
  271.   MoveWindow (hWnd,
  272.           rc->left,
  273.           rc->top,
  274.           rc->right-rc->left,
  275.           rc->bottom-rc->top,
  276.           repaint);
  277. }
  278.